package com.boomsecret.redis;

import redis.clients.jedis.Jedis;
import redis.clients.util.SafeEncoder;

import java.util.List;

/**
 * Created by wangjinliang on 2018/1/22.
 * 对存储结构为String类型的操作
 */
public final class RedisStringUtils {

    private RedisStringUtils() {}

    private static Jedis getJedis() {
        return RedisUtils.getJedis();
    }

    private static void releaseJedis(Jedis jedis) {
        RedisUtils.releaseJedis(jedis);
    }

    /**
     * 根据key获取记录
     * @param key
     * @return
     */
    public static String get(String key) {
        Jedis jedis = getJedis();
        String value = jedis.get(key);
        releaseJedis(jedis);
        return value;
    }

    /**
     * 根据key获取记录
     * @param key
     * @return
     */
    public static byte[] get(byte[] key) {
        Jedis jedis = getJedis();
        byte[] value = jedis.get(key);
        releaseJedis(jedis);
        return value;
    }

    /**
     * 添加有过期时间的记录
     * @param key
     * @param seconds 过期时间，以秒为单位
     * @param value
     * @return 操作状态
     */
    public static String setex(String key, int seconds, String value) {
        Jedis jedis = getJedis();
        String str = jedis.setex(key, seconds, value);
        releaseJedis(jedis);
        return str;
    }

    /**
     * 添加有过期时间的记录
     * @param key
     * @param seconds 过期时间，以秒为单位
     * @param value
     * @return 操作状态
     */
    public static String setex(byte[] key, int seconds, byte[] value) {
        Jedis jedis = getJedis();
        String str = jedis.setex(key, seconds, value);
        releaseJedis(jedis);
        return str;
    }

    /**
     * 添加一条记录, 仅当给定的key不存在时才插入
     * @param key
     * @param value
     * @return 状态码 1插入成功且key不存在 0未插入key存在
     */
    public static long setnx(String key, String value) {
        Jedis jedis = getJedis();
        long str = jedis.setnx(key, value);
        releaseJedis(jedis);
        return str;
    }

    /**
     * 添加记录, 如果记录已存在将覆盖原有的value
     * @param key
     * @param value
     * @return
     */
    public static String set(byte[] key, byte[] value) {
        Jedis jedis = getJedis();
        String status = jedis.set(key, value);
        releaseJedis(jedis);
        return status;
    }

    /**
     * 添加记录, 如果记录已存在将覆盖原有的value
     * @param key
     * @param value
     * @return
     */
    public static String set(String key, String value) {
        return set(SafeEncoder.encode(key), SafeEncoder.encode(value));
    }

    /**
     * 添加记录, 如果记录已存在将覆盖原有的value
     * @param key
     * @param value
     * @return
     */
    public static String set(String key, byte[] value) {
        return set(SafeEncoder.encode(key), value);
    }

    /**
     * 从指定位置开始插入数据, 插入的数据会覆盖指定位置以后的数据
     * 比如：123456789 setRange(key, 4, 0000) 结果123400009
     * @param key
     * @param offset
     * @param value
     * @return
     */
    public static long setRange(String key, long offset, String value) {
        Jedis jedis = getJedis();
        long len = jedis.setrange(key, offset, value);
        releaseJedis(jedis);
        return len;
    }

    /**
     * 在指定的key中追加value
     * @param key
     * @param value
     * @return 追加后value的长度
     */
    public static long append(String key, String value) {
        Jedis jedis = getJedis();
        long len = jedis.append(key, value);
        releaseJedis(jedis);
        return len;
    }

    /**
     * 将key对应的value减去指定的值, 只有value可以转为数字时该方法才可用
     * @param key
     * @param number 要减去的值
     * @return 减指定值后的值
     */
    public static long decrBy(String key, long number) {
        Jedis jedis = getJedis();
        long len = jedis.decrBy(key, number);
        releaseJedis(jedis);
        return len;
    }

    /**
     * 将key对应的value加上指定的值, 只有value可以转为数字时该方法才可用
     * @param key
     * @param number 要加上的值
     * @return 相加后的值
     */
    public static long incrBy(String key, long number) {
        Jedis jedis = getJedis();
        long len = jedis.incrBy(key, number);
        releaseJedis(jedis);
        return len;
    }

    /**
     * 对指定key的value进行截取
     * @param key
     * @param startOffset 开始位置(包含)
     * @param endOffset 结束位置(包含)
     * @return 截取的值
     */
    public static String getrange(String key, long startOffset, long endOffset) {
        Jedis jedis = getJedis();
        String value = jedis.getrange(key, startOffset, endOffset);
        releaseJedis(jedis);
        return value;
    }

    /**
     * 获取并设置指定key对应的value
     * @param key
     * @param value
     * @return 原始value或null
     */
    public static String getSet(String key, String value) {
        Jedis jedis = getJedis();
        String str = jedis.getSet(key, value);
        releaseJedis(jedis);
        return str;
    }

    /**
     * 批量获取记录, 如果指定的key不存在返回List的对应位置将是null
     * @param keys
     * @return 值的集合
     */
    public static List<String> mget(String... keys) {
        Jedis jedis = getJedis();
        List<String> str = jedis.mget(keys);
        releaseJedis(jedis);
        return str;
    }

    /**
     * 批量存储记录
     * @param keysvalues "key1","value1","key2","value2";
     * @return
     */
    public static String mset(String... keysvalues) {
        Jedis jedis = getJedis();
        String str = jedis.mset(keysvalues);
        releaseJedis(jedis);
        return str;
    }

    /**
     * 获取key对应的值的长度
     * @param key
     * @return value值得长度
     */
    public static long strlen(String key) {
        Jedis jedis = getJedis();
        long len = jedis.strlen(key);
        releaseJedis(jedis);
        return len;
    }
}
